﻿// Decompiled with JetBrains decompiler
// Type: TaleWorlds.MountAndBlade.View.MountVisualCreator
// Assembly: TaleWorlds.MountAndBlade.View, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
// MVID: 61152EB8-513B-4D4A-8AC0-0D1465C6CF6C
// Assembly location: D:\steam\steamapps\common\Mount & Blade II Bannerlord\Modules\Native\bin\Win64_Shipping_Client\TaleWorlds.MountAndBlade.View.dll

using System.Collections.Generic;
using TaleWorlds.Core;
using TaleWorlds.DotNet;
using TaleWorlds.Engine;
using TaleWorlds.Library;

#nullable disable
namespace TaleWorlds.MountAndBlade.View
{
  public static class MountVisualCreator
  {
    public static void SetMaterialProperties(
      ItemObject mountItem,
      MetaMesh mountMesh,
      MountCreationKey key,
      ref uint maneMeshMultiplier)
    {
      HorseComponent horseComponent = mountItem.HorseComponent;
      int index1 = MathF.Min((int) key.MaterialIndex, horseComponent.HorseMaterialNames.Count - 1);
      HorseComponent.MaterialProperty horseMaterialName = horseComponent.HorseMaterialNames[index1];
      Material fromResource = Material.GetFromResource(horseMaterialName.Name);
      if (mountItem.ItemType == ItemObject.ItemTypeEnum.Horse)
      {
        int index2 = MathF.Min((int) key.MeshMultiplierIndex, horseMaterialName.MeshMultiplier.Count - 1);
        if (index2 != -1)
          maneMeshMultiplier = horseMaterialName.MeshMultiplier[index2].Item1;
        mountMesh.SetMaterialToSubMeshesWithTag(fromResource, "horse_body");
        mountMesh.SetFactorColorToSubMeshesWithTag(maneMeshMultiplier, "horse_tail");
      }
      else
        mountMesh.SetMaterial(fromResource);
    }

    public static List<MetaMesh> AddMountMesh(
      MBAgentVisuals agentVisual,
      ItemObject mountItem,
      ItemObject harnessItem,
      string mountCreationKeyStr,
      Agent agent = null)
    {
      List<MetaMesh> metaMeshList = new List<MetaMesh>();
      HorseComponent horseComponent = mountItem.HorseComponent;
      uint maxValue = uint.MaxValue;
      MetaMesh multiMesh = mountItem.GetMultiMesh(false, false, true);
      if (string.IsNullOrEmpty(mountCreationKeyStr))
        mountCreationKeyStr = MountCreationKey.GetRandomMountKeyString(mountItem, MBRandom.RandomInt());
      MountCreationKey mountCreationKey = MountCreationKey.FromString(mountCreationKeyStr);
      if (mountItem.ItemType == ItemObject.ItemTypeEnum.Horse)
        MountVisualCreator.SetHorseColors(multiMesh, mountCreationKey);
      if (horseComponent.HorseMaterialNames != null && horseComponent.HorseMaterialNames.Count > 0)
        MountVisualCreator.SetMaterialProperties(mountItem, multiMesh, mountCreationKey, ref maxValue);
      int nondeterministicRandomInt = MBRandom.NondeterministicRandomInt;
      MountVisualCreator.SetVoiceDefinition(agent, nondeterministicRandomInt);
      MetaMesh metaMesh = (MetaMesh) null;
      if (harnessItem != null)
        metaMesh = harnessItem.GetMultiMesh(false, false, true);
      foreach (KeyValuePair<string, bool> additionalMeshesName in horseComponent.AdditionalMeshesNameList)
      {
        if (additionalMeshesName.Key.Length > 0)
        {
          string metaMeshName = additionalMeshesName.Key;
          if (harnessItem == null || !additionalMeshesName.Value)
          {
            MetaMesh copy = MetaMesh.GetCopy(metaMeshName);
            if (maxValue != uint.MaxValue)
              copy.SetFactor1Linear(maxValue);
            metaMeshList.Add(copy);
          }
          else
          {
            ArmorComponent armorComponent1 = harnessItem.ArmorComponent;
            if ((armorComponent1 != null ? (armorComponent1.ManeCoverType != ArmorComponent.HorseHarnessCoverTypes.All ? 1 : 0) : 1) != 0)
            {
              ArmorComponent armorComponent2 = harnessItem.ArmorComponent;
              if ((armorComponent2 != null ? (armorComponent2.ManeCoverType > ArmorComponent.HorseHarnessCoverTypes.None ? 1 : 0) : 0) != 0)
                metaMeshName = metaMeshName + "_" + (object) harnessItem?.ArmorComponent?.ManeCoverType;
              MetaMesh copy = MetaMesh.GetCopy(metaMeshName);
              if (maxValue != uint.MaxValue)
                copy.SetFactor1Linear(maxValue);
              metaMeshList.Add(copy);
            }
          }
        }
      }
      if ((NativeObject) multiMesh != (NativeObject) null)
      {
        if (harnessItem != null)
        {
          ArmorComponent.HorseTailCoverTypes? tailCoverType = harnessItem.ArmorComponent?.TailCoverType;
          ArmorComponent.HorseTailCoverTypes horseTailCoverTypes = ArmorComponent.HorseTailCoverTypes.All;
          if (tailCoverType.GetValueOrDefault() == horseTailCoverTypes & tailCoverType.HasValue)
            multiMesh.RemoveMeshesWithTag("horse_tail");
        }
        metaMeshList.Add(multiMesh);
      }
      if ((NativeObject) metaMesh != (NativeObject) null)
      {
        if ((NativeObject) agentVisual != (NativeObject) null)
        {
          MetaMesh ropeMesh = (MetaMesh) null;
          if (NativeConfig.CharacterDetail > 2 && harnessItem.ArmorComponent != null)
            ropeMesh = MetaMesh.GetCopy(harnessItem.ArmorComponent.ReinsRopeMesh, false, true);
          MetaMesh copy = MetaMesh.GetCopy(harnessItem.ArmorComponent?.ReinsMesh, false, true);
          if ((NativeObject) ropeMesh != (NativeObject) null && (NativeObject) copy != (NativeObject) null)
          {
            agentVisual.AddHorseReinsClothMesh(copy, ropeMesh);
            ropeMesh.ManualInvalidate();
          }
          if ((NativeObject) copy != (NativeObject) null)
            metaMeshList.Add(copy);
        }
        else if (harnessItem.ArmorComponent != null)
        {
          MetaMesh copy = MetaMesh.GetCopy(harnessItem.ArmorComponent.ReinsMesh, mayReturnNull: true);
          if ((NativeObject) copy != (NativeObject) null)
            metaMeshList.Add(copy);
        }
        metaMeshList.Add(metaMesh);
      }
      return metaMeshList;
    }

    public static void SetHorseColors(MetaMesh horseMesh, MountCreationKey mountCreationKey)
    {
      horseMesh.SetVectorArgument((float) mountCreationKey._leftFrontLegColorIndex, (float) mountCreationKey._rightFrontLegColorIndex, (float) mountCreationKey._leftBackLegColorIndex, (float) mountCreationKey._rightBackLegColorIndex);
    }

    public static void ClearMountMesh(GameEntity gameEntity)
    {
      gameEntity.RemoveAllChildren();
      gameEntity.Remove(106);
    }

    private static void SetVoiceDefinition(Agent agent, int seedForRandomVoiceTypeAndPitch)
    {
      MBAgentVisuals agentVisuals = agent?.AgentVisuals;
      if (!((NativeObject) agentVisuals != (NativeObject) null))
        return;
      string collisionInfoClassName1 = agent.GetSoundAndCollisionInfoClassName();
      int collisionInfoClassName2 = !string.IsNullOrEmpty(collisionInfoClassName1) ? SkinVoiceManager.GetVoiceDefinitionCountWithMonsterSoundAndCollisionInfoClassName(collisionInfoClassName1) : 0;
      if (collisionInfoClassName2 == 0)
      {
        agentVisuals.SetVoiceDefinitionIndex(-1, 0.0f);
      }
      else
      {
        int num = MathF.Abs(seedForRandomVoiceTypeAndPitch);
        float voicePitch = (float) num * 4.656613E-10f;
        int[] definitionIndices = new int[collisionInfoClassName2];
        SkinVoiceManager.GetVoiceDefinitionListWithMonsterSoundAndCollisionInfoClassName(collisionInfoClassName1, definitionIndices);
        int voiceDefinitionIndex = definitionIndices[num % collisionInfoClassName2];
        agentVisuals.SetVoiceDefinitionIndex(voiceDefinitionIndex, voicePitch);
      }
    }

    public static void AddMountMeshToEntity(
      GameEntity gameEntity,
      ItemObject mountItem,
      ItemObject harnessItem,
      string mountCreationKeyStr,
      Agent agent = null)
    {
      foreach (MetaMesh metaMesh in MountVisualCreator.AddMountMesh((MBAgentVisuals) null, mountItem, harnessItem, mountCreationKeyStr, agent))
      {
        gameEntity.AddMultiMeshToSkeleton(metaMesh);
        metaMesh.ManualInvalidate();
      }
    }

    public static void AddMountMeshToAgentVisual(
      MBAgentVisuals agentVisual,
      ItemObject mountItem,
      ItemObject harnessItem,
      string mountCreationKeyStr,
      Agent agent = null)
    {
      foreach (MetaMesh metaMesh in MountVisualCreator.AddMountMesh(agentVisual, mountItem, harnessItem, mountCreationKeyStr, agent))
      {
        agentVisual.AddMultiMesh(metaMesh, TaleWorlds.MountAndBlade.BodyMeshTypes.Invalid);
        metaMesh.ManualInvalidate();
      }
      if (mountItem.HorseComponent?.SkeletonScale == null)
        return;
      agentVisual.ApplySkeletonScale(mountItem.HorseComponent.SkeletonScale.MountSitBoneScale, mountItem.HorseComponent.SkeletonScale.MountRadiusAdder, mountItem.HorseComponent.SkeletonScale.BoneIndices, mountItem.HorseComponent.SkeletonScale.Scales);
    }
  }
}
